'use client';

import React, { useState, useEffect, forwardRef, useImperativeHandle } from 'react';
import {
  Card,
  Tabs,
  Typography,
  Space,
  Modal
} from 'antd';
import WeeklyTimeSelector, { ScheduleMode, ViewMode } from '@/components/WeeklyTimeSelector';
import { RoleType, InstrumentSchedule, InstrumentScheduleSpecificDate } from '@/types/instrument';
import { systemApi } from '@/apis/system';
import { ScheduleType } from '@/types/system';

const { TabPane } = Tabs;
const { Text } = Typography;

export interface TimeScheduleRef {
  getFormData: () => {
    instrumentSchedules?: InstrumentSchedule[];
    instrumentScheduleSpecificDates?: InstrumentScheduleSpecificDate[];
  };
}

interface TimeScheduleProps {
  mode?: 'create' | 'edit' | 'view';
  initialValues?: {
    instrumentSchedules?: InstrumentSchedule[];
    instrumentScheduleSpecificDates?: InstrumentScheduleSpecificDate[];
    minDuration?: number;
  };
  minDuration?: number;
}

const TimeSchedule = forwardRef<TimeScheduleRef, TimeScheduleProps>(({
  mode = 'create',
  initialValues = {},
  minDuration: propMinDuration,
}, ref) => {
  const isReadOnly = mode === 'view';
  const [activeTab, setActiveTab] = useState('regular');
    
  // 普通排期数据
  const [regularSchedules, setRegularSchedules] = useState<InstrumentSchedule[]>(
    initialValues.instrumentSchedules || []
  );
  
  // 特定日期排期数据
  const [specificDateSchedules, setSpecificDateSchedules] = useState<InstrumentScheduleSpecificDate[]>(
    initialValues.instrumentScheduleSpecificDates || []
  );

  const minDuration = propMinDuration || initialValues.minDuration || 30;

  useEffect(() => {
    if (initialValues.instrumentSchedules) {
      setRegularSchedules(initialValues.instrumentSchedules);
    }
    if (initialValues.instrumentScheduleSpecificDates) {
      setSpecificDateSchedules(initialValues.instrumentScheduleSpecificDates);
    }
  }, [initialValues]);

  // 检测时间段冲突的函数（同步版本，用于已知工作日状态的情况）
  const checkTimeConflictSync = (
    regularSchedule: InstrumentSchedule,
    specificSchedule: InstrumentScheduleSpecificDate,
    isWorkdayMap: Map<string, boolean> // 日期 -> 是否工作日的映射
  ): boolean => {
    // 检查角色类型是否匹配
    if (regularSchedule.roleType !== specificSchedule.roleType) {
      return false; // 不同角色类型，不冲突
    }

    // 检查特定日期是否关闭整天
    if (specificSchedule.dateType === 1) { // DateType.CLOSE_ALL_DAY
      return true; // 关闭整天，与任何默认时段都冲突
    }

    // 检查星期是否匹配
    const specificDate = new Date(specificSchedule.specificDate);
    const dayOfWeek = specificDate.getDay(); // 0=Sunday, 1=Monday, ..., 6=Saturday

    // 将星期天从0转换为7，以匹配后端的星期格式
    const weekDay = dayOfWeek === 0 ? 7 : dayOfWeek;

    // 检查默认排期的每个组是否与特定日期冲突
    for (const group of regularSchedule.groups) {
      let shouldCheckThisGroup = false;

      // 检查是否是工作日模式
      if (group.isWorkday === 1) {
        // 工作日模式：检查该日期是否为工作日
        const isWorkday = isWorkdayMap.get(specificSchedule.specificDate);
        if (isWorkday === true) {
          shouldCheckThisGroup = true;
        }
      } else {
        // 自定义星期模式：检查unfixDays
        const unfixDays = group.unfixDays.split(',').map(d => parseInt(d.trim()));
        if (unfixDays.includes(weekDay)) {
          shouldCheckThisGroup = true;
        }
      }

      if (!shouldCheckThisGroup) {
        continue; // 不匹配的组，跳过
      }

      // 检查时间段是否重叠
      for (const regularTimeslot of group.timeslots) {
        for (const specificTimeslot of specificSchedule.timeslots) {
          // 将时间字符串转换为分钟数进行比较
          const regularStart = timeStringToMinutes(regularTimeslot.startTime);
          const regularEnd = timeStringToMinutes(regularTimeslot.endTime);
          const specificStart = timeStringToMinutes(specificTimeslot.startTime);
          const specificEnd = timeStringToMinutes(specificTimeslot.endTime);

          // 时间段重叠检测：A.start < B.end && B.start < A.end
          if (regularStart < specificEnd && specificStart < regularEnd) {
            return true; // 发现冲突
          }
        }
      }
    }

    return false; // 没有冲突
  };

  // 将时间字符串转换为分钟数的辅助函数
  const timeStringToMinutes = (timeStr: string): number => {
    const [hours, minutes] = timeStr.split(':').map(Number);
    return hours * 60 + minutes;
  };

  // 查找所有冲突的特殊时段（异步版本）
  const findConflictingSpecificDates = async (newRegularSchedules: InstrumentSchedule[]) => {
    const conflicts: InstrumentScheduleSpecificDate[] = [];

    // 收集所有需要查询工作日状态的日期
    const datesToQuery = new Set<string>();
    for (const specificSchedule of specificDateSchedules) {
      datesToQuery.add(specificSchedule.specificDate);
    }

    // 查询工作日状态
    const isWorkdayMap = new Map<string, boolean>();
    if (datesToQuery.size > 0) {
      try {
        const dates = Array.from(datesToQuery).sort();
        const startDate = dates[0];
        const endDate = dates[dates.length - 1];

        const holidayList = await systemApi.getHolidayList({
          startDate,
          endDate
        });

        // 构建工作日映射
        for (const date of datesToQuery) {
          const dateObj = new Date(date);
          const dayOfWeek = dateObj.getDay(); // 0=Sunday, 1=Monday, ..., 6=Saturday

          // 检查是否在节假日列表中
          const holidayInfo = holidayList.find(h => h.holidayDate === date);

          if (holidayInfo) {
            // 有节假日信息，根据类型判断
            switch (holidayInfo.type) {
              case 1: // ScheduleType.HOLIDAY - 节假日
                isWorkdayMap.set(date, false);
                break;
              case 2: // ScheduleType.WORKDAY - 调休日（工作日）
                isWorkdayMap.set(date, true);
                break;
              case 3: // ScheduleType.WEEKEND - 正常周末
                isWorkdayMap.set(date, false);
                break;
              default:
                // 默认按正常工作日判断（周一到周五）
                isWorkdayMap.set(date, dayOfWeek >= 1 && dayOfWeek <= 5);
            }
          } else {
            // 没有节假日信息，按正常工作日判断（周一到周五）
            isWorkdayMap.set(date, dayOfWeek >= 1 && dayOfWeek <= 5);
          }
        }
      } catch (error) {
        console.error('查询工作日状态失败:', error);
        // 查询失败时，按正常工作日判断
        for (const date of datesToQuery) {
          const dateObj = new Date(date);
          const dayOfWeek = dateObj.getDay();
          isWorkdayMap.set(date, dayOfWeek >= 1 && dayOfWeek <= 5);
        }
      }
    }

    // 检查冲突
    for (const regularSchedule of newRegularSchedules) {
      for (const specificSchedule of specificDateSchedules) {
        if (checkTimeConflictSync(regularSchedule, specificSchedule, isWorkdayMap)) {
          // 避免重复添加（基于ID和日期）
          if (!conflicts.find(c =>
            c.specificDate === specificSchedule.specificDate &&
            c.roleType === specificSchedule.roleType &&
            c.id === specificSchedule.id
          )) {
            conflicts.push(specificSchedule);
          }
        }
      }
    }

    return conflicts;
  };

  // 处理默认排期变化，检测冲突并询问用户
  const handleRegularScheduleChange = async (newSchedules: InstrumentSchedule[]) => {
    try {
      const conflicts = await findConflictingSpecificDates(newSchedules);

      if (conflicts.length > 0) {
        // 构建冲突信息
        const conflictInfo = conflicts.map(conflict => {
          const date = conflict.specificDate;
          const timeslots = conflict.timeslots.map(t =>
            `${t.startTime.substring(0, 5)}-${t.endTime.substring(0, 5)}`
          ).join(', ');
          return `${date} (${timeslots})`;
        }).join('\n');

        Modal.confirm({
          title: '检测到时间冲突',
          content: (
            <div>
              <p>修改默认预约时段后，发现与以下特殊时段存在冲突：</p>
              <div style={{
                backgroundColor: '#fff2e8',
                padding: '12px',
                borderRadius: '6px',
                marginTop: '12px',
                whiteSpace: 'pre-line',
                fontFamily: 'monospace',
                fontSize: '13px'
              }}>
                {conflictInfo}
              </div>
              <p style={{ marginTop: '12px', color: '#fa8c16' }}>
                是否要清除这些冲突的特殊时段？
              </p>
            </div>
          ),
          okText: '是',
          cancelText: '否',
          okType: 'danger',
          onOk: () => {
            // 清除冲突的特殊时段，保留当前默认预约时间段的修改
            const remainingSpecificDates = specificDateSchedules.filter(
              specificSchedule => !conflicts.some(conflict =>
                conflict.specificDate === specificSchedule.specificDate &&
                conflict.roleType === specificSchedule.roleType &&
                conflict.id === specificSchedule.id
              )
            );

            setSpecificDateSchedules(remainingSpecificDates);
            setRegularSchedules(newSchedules);
          },
          onCancel: () => {
            // 用户选择"否"，不清除冲突的配置，但保留当前默认预约时间段的修改
            setRegularSchedules(newSchedules);
            console.log('用户选择保留冲突的特殊时段配置，同时保留默认排期的修改');
          }
        });
      } else {
        // 没有冲突，直接更新
        setRegularSchedules(newSchedules);
      }
    } catch (error) {
      console.error('检测冲突时出错:', error);
      // 出错时直接更新，不进行冲突检测
      setRegularSchedules(newSchedules);
    }
  };

  // 暴露方法给父组件
  useImperativeHandle(ref, () => ({
    getFormData: () => {
      return {
        instrumentSchedules: regularSchedules,
        instrumentScheduleSpecificDates: specificDateSchedules,
      };
    }
  }), [regularSchedules, specificDateSchedules]);

  // 使用系统API查询日期状态
  const handleQueryDayStatus = async (startDate: string, endDate: string) => {
    try {
      // 调用系统API获取节假日信息
      const holidayList = await systemApi.getHolidayList({
        startDate,
        endDate
      });
      
      // 创建日期范围内的所有日期
      const days = [];
      const start = new Date(startDate);
      const end = new Date(endDate);
      
      for (let date = new Date(start); date <= end; date.setDate(date.getDate() + 1)) {
        const dateStr = date.toISOString().split('T')[0];
        const dayOfWeek = date.getDay(); // 0=周日, 1=周一, ..., 6=周六
        
        // 查找该日期是否在节假日列表中
        const holidayInfo = holidayList.find(h => h.holidayDate === dateStr);
        
        if (holidayInfo) {
          // 如果在节假日列表中，使用API返回的类型
          days.push({
            date: dateStr,
            scheduleType: holidayInfo.type as ScheduleType,
            isWorkday: holidayInfo.type === ScheduleType.WORKDAY
          });
        } else {
          // 如果不在节假日列表中，则为普通工作日
          // 周一至周五是工作日，周六日是周末
          const isWeekend = dayOfWeek === 0 || dayOfWeek === 6;
          days.push({
            date: dateStr,
            scheduleType: isWeekend ? ScheduleType.WEEKEND : ScheduleType.WORKDAY,
            isWorkday: !isWeekend
          });
        }
      }
      
      return days;
    } catch (error) {
      console.error('获取节假日信息失败:', error);
      
      // 发生错误时返回默认数据（按周一到周五为工作日计算）
      const days = [];
      const start = new Date(startDate);
      const end = new Date(endDate);
      
      for (let date = new Date(start); date <= end; date.setDate(date.getDate() + 1)) {
        const dayOfWeek = date.getDay(); // 0=周日, 1=周一, ..., 6=周六
        const dateStr = date.toISOString().split('T')[0];
        
        // 周一到周五为工作日，周六日为周末
        const isWorkday = dayOfWeek >= 1 && dayOfWeek <= 5;
        const scheduleType = isWorkday ? ScheduleType.WORKDAY : ScheduleType.WEEKEND;
        
        days.push({
          date: dateStr,
          scheduleType,
          isWorkday
        });
      }
      
      return days;
    }
  };

  return (
    <div style={{ maxWidth: '1200px' }}>
      <Tabs 
        activeKey={activeTab} 
        onChange={setActiveTab}
      >
        <TabPane tab="默认可预约时间" key="regular">
          <Card title="默认可预约时间设置">
            <div style={{ marginBottom: 16 }}>
              <Text type="secondary">
                设置每周重复的时间模式，支持按用户级别配置不同的可预约时间。
                可以选择法定工作日（系统自动过滤节假日）或自定义星期几。
              </Text>
            </div>
            
            <WeeklyTimeSelector
              mode={ScheduleMode.REGULAR}
              readOnly={isReadOnly}
              minDuration={minDuration}
              currentUserLevel={RoleType.LEVEL_1_USER}
              scheduleData={regularSchedules}
              onScheduleChange={handleRegularScheduleChange}
            />
          </Card>
        </TabPane>
        
        <TabPane tab="自定义预约时间" key="specific">
          <Card title="自定义预约时间">

            
            <WeeklyTimeSelector
              mode={ScheduleMode.SPECIFIC_DATE}
              viewMode={ViewMode.CALENDAR}
              readOnly={isReadOnly}
              minDuration={minDuration}
              currentUserLevel={RoleType.LEVEL_1_USER}
              scheduleData={regularSchedules}
              specificDateData={specificDateSchedules}
              onSpecificDateChange={(schedules) => setSpecificDateSchedules(schedules)}
              onQueryDayStatus={handleQueryDayStatus}
            />
          </Card>
        </TabPane>
      </Tabs>

      {/* 配置摘要 */}
      {/* <Card title="配置摘要" style={{ marginTop: 16 }}>
        <Space direction="vertical" style={{ width: '100%' }}>
          <div>
            <Text strong>最小预约时长：</Text>
            <Text>{minDuration} 分钟</Text>
          </div>
          
          <div>
            <Text strong>默认排期配置：</Text>
            <Text>
              {regularSchedules.length > 0 
                ? `已配置 ${regularSchedules.length} 个用户级别的默认时间`
                : '暂未配置'
              }
            </Text>
          </div>
          
          <div>
            <Text strong>特定日期配置：</Text>
            <Text>
              {specificDateSchedules.length > 0 
                ? `已配置 ${specificDateSchedules.length} 个特定日期`
                : '暂未配置'
              }
            </Text>
          </div>
          
          <div>
            <Text strong>配置优先级：</Text>
            <Text type="secondary">
              特定日期配置 &gt; 默认配置（法定工作日/自定义星期）&gt; 无配置
            </Text>
          </div>
        </Space>
      </Card> */}
    </div>
  );
});

TimeSchedule.displayName = 'TimeSchedule';

export default TimeSchedule; 